import * as THREE from 'three'
import { AxesHelper } from 'three';
import { Scene } from 'three';
import { Mesh } from 'three';
import { MeshBasicMaterial } from 'three';
import { WebGLRenderer } from 'three';
import GUI from 'lil-gui';
import { PerspectiveCamera } from 'three';
import { BoxGeometry } from 'three';
import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'
import beyond from './public/beyond.png'
import { TextureLoader } from 'three';
import { GridHelper } from 'three';
const TWEEN = require("@tweenjs/tween.js");
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import Lbjn from './public/Lamborghini.glb'
import { AmbientLight } from 'three';
import { PlaneGeometry } from 'three';
import { MeshPhysicalMaterial } from 'three';
import { SpotLight } from 'three';
import { CylinderGeometry } from 'three';
import messi from './public/beyond.png'
//初始化场景
let scene, camera, rederer, mesh, controls, grid;
let doors = [];
let bodyMaterial = new THREE.MeshPhysicalMaterial({
    color: "yellow",
    metalness: 1,
    roughness: 0.5,
    clearcoat: 1.0,
    clearcoatRoughness: 0.03,
});
let glassMaterial = new THREE.MeshPhysicalMaterial({
    color: "#793e3e",
    metalness: 0.25,
    roughness: 0,
    transmission: 1.0 //透光性.transmission属性可以让一些很薄的透明表面，例如玻璃，变得更真实一些。
});
function init() {
    scene = new Scene();

}
//透视i相机初始化
function initCamera() {
    camera = new PerspectiveCamera(40, window.innerWidth / window.innerHeight, 0.1, 1000);

    camera.position.set(4.25, 1.4, -4.5)
}
//初始化渲染器
function initRenderer() {
    rederer = new WebGLRenderer({
        //棱角
        antialias: true
    });
    rederer.setSize(window.innerWidth, window.innerHeight);
    rederer.shadowMap.enabled = true
    document.body.appendChild(rederer.domElement);
}
// //坐标
// function initAxesHelper() {
//     const axesHelper = new AxesHelper(3);
//     scene.add(axesHelper);
// }
//轨道控制器
function initOrbitControls() {
    controls = new OrbitControls(camera, rederer.domElement);
    controls.enableDamping = true;
    controls.maxDistance = 9;
    controls.minDistance = 0
    controls.minPolarAngle = 0;
    controls.maxPolarAngle = 80 / 360 * 2 * Math.PI;
}

//物体
function initGridHelper() {
    grid = new GridHelper(20, 40, 'red', 0xfffff);
    grid.material.opacity = 0.2
    grid.material.transparent = true
    scene.add(grid)
}
function loadModel() {
    new GLTFLoader().load(Lbjn, function (gltf) {
        const carmodel = gltf.scene
        carmodel.rotation.y = Math.PI
        carmodel.traverse((obj) => {
            console.log(obj)
            if (obj.name == 'Object_103' || obj.name == 'Object_64' || obj.name == 'Object_77') {
                obj.material = bodyMaterial
                //车身
            } else if (obj.name == 'Object_90') {
                obj.material = glassMaterial
                //玻璃
            } else if (obj.name == 'Empty001_16' || obj.name == 'Empty002_20') {
                //门
                doors.push(obj)
            } else {

            }


            obj.castShadow = true;

        })
        scene.add(carmodel)
    })
}
function initAmbientLight() {
    const ambientLight = new AmbientLight('#fff', 2);
    scene.add(ambientLight)
}
function initFloor() {
    const floorCGeomatry = new PlaneGeometry(20, 20);
    const material = new MeshPhysicalMaterial({
        side: THREE.DoubleSide,
        color: 0x808080,
        //金属
        metalness: 0,
        //粗糙
        roughness: 0.1
    });
    const mesh = new Mesh(floorCGeomatry, material);
    mesh.rotation.x = Math.PI / 2
    scene.add(mesh)

}
//聚光灯
function initSpotLight() {
    // 添加头顶聚光灯
    const bigSpotLight = new SpotLight("#ffffff", 0.5);

    bigSpotLight.angle = Math.PI / 8; //散射角度，跟水平线的家教
    bigSpotLight.penumbra = 0.2;  // 聚光锥的半影衰减百分比
    bigSpotLight.decay = 2; // 纵向：沿着光照距离的衰减量。
    bigSpotLight.distance = 30;
    bigSpotLight.shadow.radius = 10;
    // 阴影映射宽度，阴影映射高度
    bigSpotLight.shadow.mapSize.set(4096, 4096);

    bigSpotLight.position.set(-5, 10, 1);
    // 光照射的方向
    bigSpotLight.target.position.set(0, 0, 0);
    bigSpotLight.castShadow = true;
    // bigSpotLight.map = bigTexture
    scene.add(bigSpotLight);
}

//圆柱体展厅
function initcy() {
    const geomart = new CylinderGeometry(12, 12, 20, 32);
    const material = new MeshPhysicalMaterial({
        color: 0x6c6c6c,
        side: THREE.DoubleSide


    })
    const cylinder = new Mesh(geomart, material);
    scene.add(cylinder)


}
function initGUI() {
    let obj = {
        bodyColor: '#6e2121',
        glassColor: '#aaa',
        carOpen,
        carClose,
        carIn,
        carOut,
    }
    const gui = new GUI();
    gui.addColor(obj, "bodyColor").name('车身颜色').onChange(value => {
        bodyMaterial.color.set(value)
    })
    gui.addColor(obj, "glassColor").name('玻璃颜色').onChange(value => {
        glassMaterial.color.set(value)
    })
    gui.add(obj, "carOpen").name('打开车门')
    gui.add(obj, "carClose").name('关闭车门')
    gui.add(obj, "carIn").name('车内视角')
    gui.add(obj, "carOut").name('车外视角')

}
function carOpen() {
    for (let index = 0; index < doors.length; index++) {

        setAnimationDoor({ x: 0 }, { x: Math.PI / 3 }, doors[index])
    }

}
function carClose() {
    for (let index = 0; index < doors.length; index++) {

        setAnimationDoor({ x: Math.PI / 3 }, { x: 0 }, doors[index])
    }
}
function setAnimationDoor(start, end, mesh) {
    const tween = new TWEEN.Tween(start).to(end, 1000).easing(TWEEN.Easing.Quadratic.Out)
    tween.onUpdate((that) => {
        mesh.rotation.x = that.x
    })
    tween.start()
}
function setAnimationCamera(start, end) {
    const tween = new TWEEN.Tween(start).to(end, 3000).easing(TWEEN.Easing.Quadratic.Out)
    tween.onUpdate((that) => {
        camera.position.set(that.cx, that.cy, that.cz)
        controls.target.set(that.ox, that.oy, that.oz)
    })
    tween.start()
}
function carIn() {
    setAnimationCamera({ cx: 4.25, cy: 1.4, cz: -4.5, ox: 0, oy: 0.5, oz: 0 }, { cx: -0.27, cy: 0.83, cz: 0.60, ox: 0, oy: 0.5, oz: -3 });
}

function carOut() {
    setAnimationCamera({ cx: -0.27, cy: 0.83, cz: 0.6, ox: 0, oy: 0.5, oz: -3 }, { cx: 4.25, cy: 1.4, cz: -4.5, ox: 0, oy: 0.5, oz: 0 });
}
function createSpotlight(color) {
    const newObj = new SpotLight(color, 2);
    newObj.castShadow = true;
    newObj.angle = Math.PI / 6;;
    newObj.penumbra = 0.2;
    newObj.decay = 2;
    newObj.distance = 50;
    return newObj;
}

function initbeyond() {
    const spotLight1 = createSpotlight('#ffffff');
    const texture = new TextureLoader().load(messi)

    spotLight1.position.set(0, 3, 0);
    spotLight1.target.position.set(-10, 3, 10)

    spotLight1.map = texture
    lightHelper1 = new THREE.SpotLightHelper(spotLight1);
    scene.add(spotLight1);
}
function initt() {
    init()
    initCamera()
    initRenderer()
    // initAxesHelper()
    initOrbitControls()
    // initGridHelper()
    loadModel()
    initAmbientLight()
    initFloor()
    initSpotLight()
    initbeyond()
    initcy()
    initGUI()

}
initt()
//旋转动画等
function render(time) {
    //动画
    // if(mesh.position.x>3){

    // }else{
    //     mesh.position.x+=0.01;

    // }

    rederer.render(scene, camera)
    requestAnimationFrame(render)
    TWEEN.update(time)
    controls.update(time)
}
render()
window.addEventListener('resize', function () {
    //camera全局适配
    camera.aspect = window.innerWidth / window.innerHeight;
    camera.updateProjectionMatrix()
    //renderer
    rederer.setSize(window.innerWidth, window.innerHeight)
})

// window.addEventListener('click', onPointClick);
// function onPointClick(event) {
//     let pointer = {}
//     pointer.x = (event.clientX / window.innerWidth) * 2 - 1;
//     pointer.y = - (event.clientY / window.innerHeight) * 2 + 1;


//     var vector = new Vector2(pointer.x, pointer.y)
//     var raycaster = new Raycaster()
//     raycaster.setFromCamera(vector, camera)
//     let intersects = raycaster.intersectObjects(scene.children);


//     intersects.forEach((item) => {
//         if (item.object.name === 'Object_64' || item.object.name === 'Object_77') {
//             if (!carStatus || carStatus === 'close') {
//                 carOpen()
//             } else {
//                 carClose()
//             }
//             console.log(intersects)
//         }
//     })


// }